package com.common.base.web;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.struts.action.*;
import org.apache.struts.actions.DispatchAction;

import com.common.context.ApplicationContextUtil;
import com.common.converter.ConvertRegister;
import com.common.exception.BusinessException;
import com.common.util.FileUtil;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;


import java.io.IOException;
import java.io.InputStream;

public abstract class BaseAction extends DispatchAction {
    protected final Log log = LogFactory.getLog(getClass());

    static {
        new ConvertRegister();
    }

    public ActionForward execute(ActionMapping mapping,
                                 ActionForm form,
                                 HttpServletRequest request,
                                 HttpServletResponse response) {
        ActionForward forward = null;
        try {
            String actionMethod = getActionMethodByURI(request);
            forward = dispatchMethod(mapping, form, request, response, actionMethod);
        } catch (BusinessException be) {
            processBusinessException(request, be);
        } catch (Exception e) {
            processUnknownException(request, e);
        }

        if (forward == null) {
            if (mapping.findForward("failure") != null) {
                return mapping.findForward("failure");
            } else {
                return mapping.findForward("upexpected");
            }
        }

        return forward;
    }

    protected Object getBean(String beanId) {
        return ApplicationContextUtil.getBean(beanId);
    }


    private String getActionMethodByURI(HttpServletRequest request) {
        String uri = request.getRequestURI();
        String full_action = uri.substring(uri.lastIndexOf("/") + 1, uri.length());
        return full_action.substring(0, full_action.indexOf(".do"));
    }

    // Message Handler
    protected void saveActionErrorMessage(HttpServletRequest request, String strMsg) {
        saveActionErrorMessage(request, strMsg, null);
    }

    protected void saveActionErrorMessage(HttpServletRequest request, String strMsg, String[] args) {
        ActionMessages msgs = new ActionMessages();
        msgs.add(ActionMessages.GLOBAL_MESSAGE, new ActionMessage(strMsg, args));
        saveErrors(request.getSession(), msgs);
    }

    protected void processBusinessException(HttpServletRequest request, BusinessException be) {
        if (be != null) {
            log.error(be);
            if (be.getArguments() == null) {
                saveActionErrorMessage(request, be.getMessage());
            } else {
                String [] argValues = new String[be.getArguments().length];
                for (int i = 0; i < be.getArguments().length; i++) {
                    if (be.isI18nArgument(i)) {
                        argValues[i] = getResources(request).getMessage(be.getI18nArgumentKey(i));
                    } else {
                        argValues[i] = be.getArgument(i);
                    }
                }
                saveActionErrorMessage(request, be.getMessage(), argValues);
            }
        }
    }

    protected void processUnknownException(HttpServletRequest request, Exception e) {
        if (e != null) {
            e.printStackTrace();
            saveActionErrorMessage(request, "common.page.msg.unexcepted");
        }
    }

    protected void downLoadFiles(HttpServletRequest request, 
                                 HttpServletResponse response,
                                 String oringalFileName) {
        try {
            InputStream fileFullPathName = request.getSession().getServletContext()
                                                .getResourceAsStream("/files/"+oringalFileName);
            response.setContentType("xls");
            response.addHeader("Content-Disposition", "attachment;filename=" + oringalFileName);
            FileUtil.writeStream2Stream(fileFullPathName, response.getOutputStream());
        } catch (IOException e) {
            throw new BusinessException("errors.stoass.ImportFile.downLoad");
        }
    }
}
